#ifndef SUDOKUFORM_H
#define SUDOKUFORM_H

#include <QWidget>
#include <map>
#include <QPaintEvent>
#include <QResizeEvent>
#include <vector>
#include "sudoku_ui_global.h"

namespace sudoku_ui {

    class SudokuCell;
    class NineSquareGrid;

    /**
     * @brief The SudokuForm class  数独游戏窗体
     */
    class SUDOKU_UI_EXPORT SudokuForm : public QWidget
    {
        Q_OBJECT
    public:
        explicit SudokuForm(QWidget *parent = nullptr);
        virtual ~SudokuForm();

        void setNumber(int num);
        void setNumber(bool state, int num);
        void setNumbers(const std::vector<std::vector<int>> &nums);

        std::vector<std::vector<int>> getNumbers();

        /**
         * @brief isOk  当检查没有错误时，检查是否已经填充完毕
         * @return
         */
        bool isOk();

        /**
         * @brief count    剩余的单元格数量
         * @param num
         * @return
         */
        int remainCount(int num);

        /**
         * @brief newGame
         */
        void newGame();

        /**
         * @brief checkGame 检查游戏结束后判断是否正确
         * @return 如果字典即为空
         */
        std::vector<std::pair<int, int>> checkGame();

    private:
        /**
         * @brief m_board   数独棋盘
         */
        std::map<int, NineSquareGrid*> m_board;

        /**
         * @brief m_cellmap 同一数字的单元格
         */
        std::map<int, std::vector<SudokuCell*>> m_cellmap;
        /**
         * @brief m_selectedGrid    选中的九宫格对象
         */
        NineSquareGrid * m_selectedGrid{nullptr};

        /**
         * @brief m_selectedCell    选中的数独单元格对象
         */
        SudokuCell * m_selectedCell{nullptr};

        /**
         * @brief toGridIndex
         * @param row
         * @param col
         * @return
         */
        int toGridIndex(int row, int col);

        /**
         * @brief toCellIndex
         * @param row
         * @param col
         * @return
         */
        int toCellIndex(int row, int col);

    signals:

    private slots:
        void onSelectedCell(SudokuCell * cell);
        void onSelectedNineGrid(NineSquareGrid * grid);
        void onCheck();
        void onAppendCell(int num, SudokuCell * cell);
        void onRemoveCell(int num, SudokuCell * cell);

    public slots:
        /**
         * @brief check     检查数独游戏
         */
        void check();

        // QWidget interface
    protected:
        void paintEvent(QPaintEvent *event) override;
        void resizeEvent(QResizeEvent *event) override;
    };


}


#endif // SUDOKUFORM_H
